package cn.xeblog.commons.util;

import io.protostuff.LinkedBuffer;
import io.protostuff.ProtobufIOUtil;
import io.protostuff.Schema;
import io.protostuff.runtime.RuntimeSchema;

/**
 * 基于Protostuff的序列化工具
 *
 * @author anlingyi
 * @date 2021/8/28 5:17 下午
 */
public class ProtostuffUtils {

    /**
     * 序列化
     *
     * @param obj 序列化对象
     * @param <T>
     * @return 序列化的字节
     */
    public static <T> byte[] serialize(T obj) {
        // 通过对象的类构建对应的schema
        Schema<T> schema = (Schema<T>) RuntimeSchema.getSchema(obj.getClass());
        // 使用LinkedBuffer分配一块默认大小的buffer空间
        LinkedBuffer buffer = LinkedBuffer.allocate();
        try {
            // 使用给定的schema将对象序列化为一个byte数组
            return ProtobufIOUtil.toByteArray(obj, schema, buffer);
        } finally {
            buffer.clear();
        }
    }

    /**
     * 反序列化
     *
     * @param bytes 字节
     * @param clazz 指定类
     * @param <T>   反序列化后的类型
     * @return 反序列化生成指定类的对象
     */
    public static <T> T deserialize(byte[] bytes, Class<T> clazz) {
        // 通过对象的类构建对应的schema
        Schema<T> schema = RuntimeSchema.getSchema(clazz);
        // 实例化类的对象
        T msg = schema.newMessage();
        // 使用给定的schema将byte数组和对象合并
        ProtobufIOUtil.mergeFrom(bytes, msg, schema);
        return msg;
    }

}
